package com.atguigu.guli.service.trade.service.impl;

import com.atguigu.guli.common.base.result.ResultCodeEnum;
import com.atguigu.guli.service.base.dto.CourseDto;
import com.atguigu.guli.service.base.dto.MemberDto;
import com.atguigu.guli.service.base.exception.MyException;
import com.atguigu.guli.service.trade.entity.Order;
import com.atguigu.guli.service.trade.entity.PayLog;
import com.atguigu.guli.service.trade.feign.EduCourseFeign;
import com.atguigu.guli.service.trade.feign.UcenterMemberFeign;
import com.atguigu.guli.service.trade.mapper.OrderMapper;
import com.atguigu.guli.service.trade.mapper.PayLogMapper;
import com.atguigu.guli.service.trade.service.OrderService;
import com.atguigu.guli.service.trade.util.OrderNoUtils;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.google.gson.Gson;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * <p>
 * 订单 服务实现类
 * </p>
 *
 * @author zero
 * @since 2020-05-30
 */
@Service
public class OrderServiceImpl extends ServiceImpl<OrderMapper, Order> implements OrderService {

    @Autowired
    private UcenterMemberFeign ucenterMemberFeign;
    @Autowired
    private EduCourseFeign eduCourseFeign;
    @Autowired
    private PayLogMapper payLogMapper;

    /**
     * 创建订单
     *
     * @param courseId 课程信息
     * @param memberId       会员id
     * @return 订单id
     */
    @Override
    public String saveOrder(String courseId, String memberId) {
        // 查询当前用户是否已有当前课程订单
        QueryWrapper<Order> orderQueryWrapper = new QueryWrapper<>();
        orderQueryWrapper.eq("course_id", courseId);
        orderQueryWrapper.eq("member_id", memberId);
        Order order = baseMapper.selectOne(orderQueryWrapper);
        if (order != null) {
            // 如果存在，则直接返回订单id
            return order.getId();
        }
        // 查询课程信息
        CourseDto courseDto = eduCourseFeign.getCourseDtoById(courseId);
        if (courseDto == null) {
            throw new MyException(ResultCodeEnum.PARAM_ERROR);
        }
        // 查询用户信息
        MemberDto memberDto = ucenterMemberFeign.getMemberDtoByMemberId(memberId);
        if (memberDto == null) {
            throw new MyException(ResultCodeEnum.PARAM_ERROR);
        }

        // 创建订单
        Order newOrder = new Order();
        newOrder.setOrderNo(OrderNoUtils.getOrderNo());
        newOrder.setCourseId(courseId);
        newOrder.setCourseTitle(courseDto.getTitle());
        newOrder.setCourseCover(courseDto.getCover());
        newOrder.setTeacherName(courseDto.getTeacherName());
        // 价格按照： 分   计算
        newOrder.setTotalFee(courseDto.getPrice().multiply(new BigDecimal(100)));
        newOrder.setMemberId(memberId);
        newOrder.setNickname(memberDto.getNickname());
        newOrder.setMobile(memberDto.getMobile());
        // 微信支付
        newOrder.setPayType(1);
        // 未支付
        newOrder.setStatus(0);
        baseMapper.insert(newOrder);
        return newOrder.getId();
    }

    /**
     * 根据用户id查询自己的订单
     *
     * @param orderId  订单id
     * @param memberId 用户id
     * @return 查询信息
     */
    @Override
    public Order getByOrderId(String orderId, String memberId) {
        QueryWrapper<Order> orderQueryWrapper = new QueryWrapper<>();
        orderQueryWrapper.eq("id", orderId).eq("member_id", memberId);
        return baseMapper.selectOne(orderQueryWrapper);
    }

    /**
     * 查询课程是否已购买
     *
     * @param courseId 课程id
     * @param memberId 用户id
     * @return 购买结果
     */
    @Override
    public Boolean isBuyByCourseId(String courseId, String memberId) {
        QueryWrapper<Order> orderQueryWrapper = new QueryWrapper<>();
        orderQueryWrapper
                .eq("course_id", courseId)
                .eq("member_id", memberId)
                .eq("status", 1);

        Integer count = baseMapper.selectCount(orderQueryWrapper);
        return count > 0;
    }

    /**
     * 获取当前用户的订单列表
     *
     * @param memberId 用户id
     * @return 订单列表
     */
    @Override
    public List<Order> selectByMemberId(String memberId) {
        QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
        queryWrapper.orderByDesc("gmt_create");
        queryWrapper.eq("member_id", memberId);
        return baseMapper.selectList(queryWrapper);
    }

    /**
     * 根据用户id删除订单
     *
     * @param orderId  订单id
     * @param memberId 用户id
     * @return 删除结果
     */
    @Override
    public boolean removeById(String orderId, String memberId) {
        QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
        queryWrapper
                .eq("id", orderId)
                .eq("member_id", memberId);
        return this.remove(queryWrapper);
    }

    /**
     * 根据订单号查询订单信息
     *
     * @param orderNo 订单号
     * @return 订单信息
     */
    @Override
    public Order getOrderByOrderNo(String orderNo) {
        QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("order_no", orderNo);
        return baseMapper.selectOne(queryWrapper);
    }

    /**
     * 更新订单状态
     *
     * @param resultMap 返回结果
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateOrderStatus(Map<String, String> resultMap) {
        //更新订单状态
        String orderNo = resultMap.get("out_trade_no");
        Order order = this.getOrderByOrderNo(orderNo);
        //支付成功
        order.setStatus(1);
        baseMapper.updateById(order);

        //记录支付日志
        PayLog payLog = new PayLog();
        payLog.setOrderNo(orderNo);
        payLog.setPayTime(new Date());
        //支付类型
        payLog.setPayType(1);
        //总金额(分)
        payLog.setTotalFee(Long.parseLong(resultMap.get("total_fee")));
        //支付状态
        payLog.setTradeState(resultMap.get("result_code"));
        payLog.setTransactionId(resultMap.get("transaction_id"));
        payLog.setAttr(new Gson().toJson(resultMap));
        payLogMapper.insert(payLog);

        //更新课程销量：有问题直接熔断
        eduCourseFeign.updateBuyCountById(order.getCourseId());
    }

    @Override
    public boolean queryPayStatus(String orderNo) {
        QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("order_no", orderNo);
        Order order = baseMapper.selectOne(queryWrapper);
        return order.getStatus() == 1;
    }
}
